package com.freesun.shop.service.imp;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;

import com.freesun.shop.service.SysRoleService;
import com.freesun.shop.entity.SysRole;
import com.freesun.shop.entity.SysRoleMenu;
import com.freesun.shop.entity.SysUserRole;
import com.freesun.shop.mapper.SysRoleMapper;
import com.freesun.shop.mapper.SysRoleMenuMapper;
import com.freesun.shop.mapper.SysUserRoleMapper;
import com.freesun.shop.vo.Auth;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.Assert;
import org.springframework.util.StringUtils;

import java.io.Serializable;
import java.time.LocalDateTime;
import java.util.Collection;
import java.util.List;

/**
 * <p>
 * 角色 服务实现类
 * </p>
 *
 * @author zf
 * @since 2019-11-13
 */
@Service
public class SysRoleServiceImpl extends ServiceImpl<SysRoleMapper, SysRole> implements SysRoleService {

    private static Logger log = LoggerFactory.getLogger(SysRoleServiceImpl.class);
    @Autowired
    private SysRoleMapper sysRoleMapper;
    @Autowired
    private SysUserRoleMapper sysUserRoleMapper;
    @Autowired
    private SysRoleMenuMapper sysRoleMenuMapper;
    @Autowired
    private StringRedisTemplate redisTemplate;
    @Override
    public IPage<SysRole> page(SysRole sysRole, Page<SysRole> page) {
        log.info("条件分页查询角色,当前页{},每页的大小{}",page.getCurrent(),page.getSize());
        IPage<SysRole> sysRoleIPage = sysRoleMapper.selectPage(page, new LambdaQueryWrapper<SysRole>()
                .like(StringUtils.hasText(sysRole.getRoleName()), SysRole::getRoleName, sysRole.getRoleName()));
        return sysRoleIPage;
    }

    @Override
    public boolean removeByIds(Collection<? extends Serializable> idList) {

        //该角色有对应的用户，不允许删除
        Integer count = sysUserRoleMapper.selectCount(new LambdaQueryWrapper<SysUserRole>()
                .in(idList != null && !idList.isEmpty(), SysUserRole::getRoleId, idList));
        if(null!=count&&count>0){
            throw new RuntimeException("删除的角色里面,还有对应的用户");
        }
        //删除role表里面的数据
        boolean flag = super.removeByIds(idList);
        //删除用户的角色关系表
        //删除角色和菜单的关系表
        sysRoleMenuMapper.delete(new LambdaQueryWrapper<SysRoleMenu>()
                .in(idList != null && !idList.isEmpty(), SysRoleMenu::getRoleId,idList));
        return flag;
    }

    @Override
    @Transactional
    public boolean save(SysRole entity) {
        System.out.println("entity = " + entity);
        entity.setCreateTime(LocalDateTime.now());
        boolean flag = super.save(entity);//新增一个角色
        List<Object> menuIdList = entity.getMenuIdList();
        if(menuIdList!=null&&!menuIdList.isEmpty()){
            menuIdList.forEach(menuId->{
                SysRoleMenu sysRoleMenu=new SysRoleMenu();
                sysRoleMenu.setMenuId(Long.valueOf(menuId.toString()));
                sysRoleMenu.setRoleId(entity.getRoleId());
                sysRoleMenuMapper.insert(sysRoleMenu);
            });
        }
        return flag;
    }

    @Override
    public SysRole getById(Serializable id) {
        SysRole sysRole = super.getById(id);
        List<Object> list = sysRoleMenuMapper.selectObjs(new LambdaQueryWrapper<SysRoleMenu>()
                .select(SysRoleMenu::getMenuId)
                .eq(SysRoleMenu::getRoleId, id));
        sysRole.setMenuIdList(list);
        return sysRole;
    }

    @Override
    public boolean updateById(SysRole entity) {
        Assert.notNull(entity,"修改的数据不能为Null");
        Assert.notNull(entity.getRoleId(),"修改数据的ID不能为null");
        SysRole sysRoleDb = getById(entity.getRoleId());
        if(null==sysRoleDb){
            throw new RuntimeException("修改的数据不存在");
        }
        //修改role表里面的数据
        boolean flag = super.updateById(entity);
        //修改了角色数据后面得操作
        List<Object> menuIdListDb = sysRoleDb.getMenuIdList();  //Long
        List<Object> menuIdListCurrent = entity.getMenuIdList(); //Integer

        boolean equeals = true;
        if(menuIdListDb.size()==menuIdListCurrent.size()){
            for (Object object : menuIdListCurrent) {
                Long aLong = Long.valueOf(object.toString());
                if(!menuIdListDb.contains(aLong)){
                    equeals=false;
                }
            }
        }else {
            equeals=false;
        }
        if (!equeals) {
            if(!menuIdListDb.isEmpty()){
                //当前和数据数据不相等，删除数据库的数据
                 sysRoleMenuMapper.delete(new LambdaQueryWrapper<SysRoleMenu>()
                        .eq(SysRoleMenu::getRoleId, entity.getRoleId()));
            }
            //新增角色菜单关系数据
            menuIdListCurrent.forEach((menuId)->{
                SysRoleMenu sysRoleMenu=new SysRoleMenu();
                sysRoleMenu.setRoleId(entity.getRoleId());
                sysRoleMenu.setMenuId(Long.valueOf(menuId.toString()));
                sysRoleMenuMapper.insert(sysRoleMenu);
            });
            //修改了角色信息，对menu的影响
            List<Object> userIds = sysUserRoleMapper.selectObjs(new LambdaQueryWrapper<SysUserRole>()
                    .select(SysUserRole::getUserId)
                    .eq(SysUserRole::getRoleId, entity.getRoleId()));
            if (null != userIds && !userIds.isEmpty()) {
                //删除这些用户的菜单和角色
                userIds.forEach((userId)->{
                    //删除缓存权限信息
                    redisTemplate.delete(Auth.USER_AUTH_PREFIX+userId);
                    redisTemplate.delete("com.freesun.shop.vo.MenuAuths::"+userId);
                });
            }
        }
        return flag;
    }
}
